package extration;

import java.io.BufferedReader;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.Comparator;
import java.util.HashMap;
import java.util.Map.Entry;

public class Data {
	//Texte a analyse
	private static String file = "./touite/train.txt";
	private static String test = "./touite/test.txt";
	//stopword
	private static String STOP_WORD = "./touite/stopWords";
	private ArrayList<String> stopwords = new ArrayList<String>(); 
	//Les messages trouve dans le textes
	protected ArrayList<Message> lesMessages;
	//Les mots trouvees dans le texte
	protected ArrayList<Mot> lesMots;
	protected ArrayList<Message> lesMessagesTest;
	protected ArrayList<Mot> lesMotsTest;
	//Les polarite des messages
	protected HashMap <String, Polarite> polarites;
	
	//Partie statistiques
	private ArrayList<Mot> topFrequents;
	public static int TOP = 20;
	private int nbMotTotal;
	private double longueurMoyenne;
	
	
	public static String POSITIVE ="positive";
	public static String NEGATIVE ="negative";
	public static String NEUTRAL ="neutral";
	public static String IRRELEVANT ="irrelevant";
		
	
	public Data(){
		lesMessages = new ArrayList<Message>();
		lesMots = new ArrayList<Mot>();
		lesMessagesTest = new ArrayList<Message>();
		lesMotsTest = new ArrayList<Mot>();
		polarites = new HashMap <String, Polarite>();
		polarites.put(POSITIVE, new Polarite(POSITIVE));
		polarites.put(NEGATIVE, new Polarite(NEGATIVE));
		polarites.put(NEUTRAL, new Polarite(NEUTRAL));
		polarites.put(IRRELEVANT, new Polarite(IRRELEVANT));
		listeStopword();
	}
	
	//Lecture et traitement du ficher
	public void readfileTest(){
		try {
			InputStream ips = new FileInputStream(test);
			InputStreamReader ipsr=new InputStreamReader(ips);
			BufferedReader br=new BufferedReader(ipsr);
			String line;
			while ((line=br.readLine())!=null){
				Message m = new Message();
				String[] mots = line.split("\",\"");
				String laChaine = mots[0].replaceAll("\"", "");
				m.setTopic(laChaine);
				laChaine = mots[1].replaceAll("\"", "");
				m.setId(laChaine);
				laChaine = mots[3].replaceAll("\"", "");
				traitementLigne(laChaine, m);
			}
			br.close(); 
		} catch (FileNotFoundException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		} 
	}
	
	//Lecture du fichier test.txt
	public void readfile(){
		try {
			InputStream ips = new FileInputStream(file);
			InputStreamReader ipsr=new InputStreamReader(ips);
			BufferedReader br=new BufferedReader(ipsr);
			String line;
			while ((line=br.readLine())!=null){
				Message m = new Message();
				String[] mots = line.split("\",\"");
				String laChaine = mots[0].replaceAll("\"", "");
				m.setTopic(laChaine);
				laChaine = mots[1].replaceAll("\"", "");
				m.setSentiment(laChaine);
				laChaine = mots[2].replaceAll("\"", "");
				m.setId(laChaine);
				laChaine = mots[4].replaceAll("\"", "");
				traitementChaine(laChaine, m);
				
				
			}
			br.close(); 
		} catch (FileNotFoundException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		} 
	}
	
	//Traitement du tweetText contenu dans le message du fichier test
		public void traitementLigne(String laChaine, Message m){
			String[] motMessage = laChaine.split(" ");
			for(int i=0; i<motMessage.length;i++){
				if(motMessage[i].length()>0){
					ajoutListeTest(motMessage[i]);
					Mot mot = getMot(motMessage[i]);
					if(mot==null)
						 mot = getMotTest(motMessage[i]);
					if(mot!=null){
						mot.addOccGenerale();
						m.addMot(mot, null);
					}
				}
			}
			lesMessagesTest.add(m);	
		}
		
	//Traitement du tweetText contenu dans le message
	public void traitementChaine(String laChaine, Message m){
		String[] motMessage = laChaine.split(" ");
		for(int i=0; i<motMessage.length;i++){
			if(motMessage[i].length()>0){
				ajoutListe(motMessage[i]);
				Mot mot = getMot(motMessage[i]);
				if(mot!=null){
					mot.addOccGenerale();
					mot.addOccPolarite(m.getSentiment());
					m.addMot(mot, m.getSentiment());
				}
			}
		}
		lesMessages.add(m);
		Polarite p = polarites.get(m.getSentiment());
		p.ajoutMessage(m);
		
		
	}
	
	//Recuperation des stopword
	private void listeStopword(){
		try {
			InputStream ips = new FileInputStream(STOP_WORD);
			InputStreamReader ipsr=new InputStreamReader(ips);
			BufferedReader br=new BufferedReader(ipsr);
			String line;
			while ((line=br.readLine())!=null){
				this.stopwords.add(line);
			}
		} catch (FileNotFoundException e) {
				e.printStackTrace();
		} catch (IOException e) {
				e.printStackTrace();
		}
		
		
	}
	
	//Traitement des mots avec les stopwords
	public String traitement(String mot){
		String modif = mot;
		String chaine=mot;
		String test = mot;
		for(String s: stopwords){
			if(modif.contains(s)){
				modif = chaine.replace(s,"");
				chaine = modif;
				
			}
		}
		return modif;
	}
	
	//Ajout des mots trouve dans le tweetText dans la listeMot si il n'existe pas deja
	public void ajoutListe(String mot){
		String m = mot;
		if(m.length()>0){
			boolean trouve = false;
			for(int i=0; i<lesMots.size() && !trouve; i++){
				if(lesMots.get(i).getChaine().equalsIgnoreCase(m)){
					trouve = true;
				}
			}
			if(!trouve || lesMots.isEmpty()){
				Mot leMot = new Mot(m);
				lesMots.add(leMot);
			}
		}
	}
	
	//Ajout des mots trouve dans le tweetText dans la listeMot si il n'existe pas deja fichier test
		public void ajoutListeTest(String mot){
			String m = mot;
			if(m.length()>0){
				boolean trouve = false;
				for(int i=0; i<lesMotsTest.size() && !trouve; i++){
					if(lesMotsTest.get(i).getChaine().equalsIgnoreCase(m)){
						trouve = true;
					}
				}
				if(!trouve || lesMotsTest.isEmpty()){
					Mot leMot = new Mot(m);
					lesMotsTest.add(leMot);
				}
			}
		}
	
	//Recuperation de l'objet Mot trouve grace a la chaine du mot
	public Mot getMot(String mot){
		Mot leMot = null;
		String m = mot;
		for(int i=0; i<lesMots.size(); i++){
			if(lesMots.get(i).getChaine().equalsIgnoreCase(m)){
				return lesMots.get(i);
			}
		}
		return leMot;
	}
	
	//Recuperation de l'objet Mot trouve grace a la chaine du mot test
		public Mot getMotTest(String mot){
			Mot leMot = null;
			String m = mot;
			for(int i=0; i<lesMotsTest.size(); i++){
				if(lesMotsTest.get(i).getChaine().equalsIgnoreCase(m)){
					return lesMotsTest.get(i);
				}
			}
			return leMot;
		}
	
	//Calcul du nombre de document global
	public int nbDocument(){
		int nb=0;
		for(Entry<String, Polarite> liste: polarites.entrySet()){
			Polarite p = liste.getValue();
			nb+= p.getMessages().size();
		}
		return nb;
	}
	
	//Calcul general du khi
	public void calculKhi(){
		int nbDocuments = this.nbDocument();
		
			for(Entry<String, Polarite> liste: polarites.entrySet()){
				Polarite p = liste.getValue();
				p.effectifMot(nbDocuments);
				
			}
	}
	
	//Partie statistiques
	
	// Les 20 plus frequents polarite confondues
	public ArrayList<Mot> calculTopFrequent(){
		this.topFrequents = new ArrayList<Mot>();
		Collections.sort(lesMots,new MyComparator());
		int taille = this.topFrequents.size();
		for(int i=0; i<this.lesMots.size() && taille < TOP; i++){
			this.topFrequents.add(lesMots.get(i));	
			taille = this.topFrequents.size();
		}
		return this.topFrequents;
	}
	//les 20 plus significatives par polarite
	public void calculTopSignificative(){
		for(Entry<String,Polarite> hm : polarites.entrySet()){
			hm.getValue().calculTopSignificatives();
			for(Mot m : hm.getValue().getTopSignificatif()){
				System.out.println(m.getChaine() + " khi " + m.getKhiPolarite(hm.getKey()));
			}
		}
	}
	
	//les 20 moins significatives par polarite
	public void calculTFlopSignificative(){
		for(Entry<String,Polarite> hm : polarites.entrySet()){
			hm.getValue().calculFlopSignificatives();
			for(Mot m : hm.getValue().getFlopSignificatif()){
				System.out.println(m.getChaine() + " khi " + m.getKhiPolarite(hm.getKey()));
			}
		}
	}

	//Le nombre de mot au total
	public int getNbMotTotal(){
		this.nbMotTotal = 0;
		for(Mot m : this.lesMots){
			this.nbMotTotal+= m.getNbOccGenerale();
		}
		return this.nbMotTotal;
	}
	//Le nombre de mot different
	public int getNbMot(){
		return this.lesMots.size();
	}
	
	//la longueur moyenne d'un message
	public double calculLongueur(){
		double nbMot = 0.0;
		this.longueurMoyenne =0.0;
		for(Message msg : lesMessages){
			nbMot+= msg.getListeMot().size();
		}
		System.out.println(nbMot + " / " + lesMessages.size() );
		this.longueurMoyenne = nbMot / (double)lesMessages.size();
		return (this.longueurMoyenne);
	}
	
	
	
	//Enlever les mots significatif
	public void removeMot(ArrayList<Mot> top){
		lesMots.removeAll(top);
		for(Message msg : lesMessages){
			msg.removeMot(top);
		}
		for(Entry<String,Polarite> hm : this.polarites.entrySet()){
			hm.getValue().removeMot(top);
		}
		
	}
	
	//getter
	public HashMap<String,Polarite> getPolarite(){
		return polarites;
	}
	public ArrayList<Mot> getLesMots(){
		return this.lesMots;
	}
	public ArrayList<Message> getLesMessages(){
		return this.lesMessages;
	}
	public ArrayList<Message> getLesMessagesTest(){
		return this.lesMessagesTest;
	}
	public ArrayList<Mot> getLesMotsTest(){
		return this.lesMotsTest;
	}

	
	
}